package com.jdd.modules.userstaff.service.impl;

import cn.hutool.core.io.IoUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.jdd.common.constant.Send;
import com.jdd.common.entity.MqttUser;
import com.jdd.common.util.LoginUserUtils;
import com.jdd.common.util.OssUtil;
import com.jdd.feign.MqttFegin;
import com.jdd.modules.device.entity.TDevice;
import com.jdd.modules.device.service.TDeviceService;
import com.jdd.modules.deviceLog.service.ITUserCmdLogService;
import com.jdd.modules.mqtt.utils.MqttCmdUtill;
import com.jdd.modules.userOptionLog.entity.TUserOptionLog;
import com.jdd.modules.userOptionLog.service.ITUserOptionLogService;
import com.jdd.modules.userstaff.dto.UserDto;
import com.jdd.modules.userstaff.entity.TUserDevice;
import com.jdd.modules.userstaff.entity.User;
import com.jdd.modules.userstaff.mapper.UserMapper;
import com.jdd.modules.userstaff.service.ITUserDeviceService;
import com.jdd.modules.userstaff.service.IUserService;
import com.jdd.utils.SnowFlakeUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;


import javax.annotation.Resource;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.Part;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @Description: 人员
 * @Author: jdd
 * @Date: 2022-03-23
 * @Version: V1.0
 */
@Slf4j
@Service
public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements IUserService {
    @Resource
    private ITUserCmdLogService userCmdLogService;

    @Resource
    private ITUserOptionLogService userOptionLogService;

    @Resource
    private MqttFegin fegin;
    @Resource
    private TDeviceService deviceService;
    @Resource
    ITUserDeviceService userDeviceService;
    @Autowired
    private OssUtil ossUtil;

    @Override
    public IPage<UserDto> findAllUserInfo(Page<UserDto> page, UserDto userDto) {
        IPage<UserDto> userDtoInfo = baseMapper.findAllUserInfo(page, userDto);

        return userDtoInfo;
    }

    @Override
    public List<String> getBindedDevice(String userId) {
        LambdaQueryWrapper<TUserDevice> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(TUserDevice::getUserId, userId);
        List<TUserDevice> list = userDeviceService.list(lambdaQueryWrapper);
        if (list == null) {
            return new ArrayList<>();
        }
        return list.stream().map(TUserDevice::getDeviceId).distinct().collect(Collectors.toList());
    }

    /*添加人员*/
    @Override
    public void createUser(String userId, List<String> split,String compareStr,Integer optionType) {
        User user = null;
        if (userId != null) {
            log.info("创建人脸接口传入的userid为：" + userId);
            user = this.getById(userId);
        } else {
            log.error("创建人脸服务接口传入的userId为空");
            return;
        }
        //封装请求体
        MqttUser mqttUser = new MqttUser();
        mqttUser.setFaceId(user.getId());
        mqttUser.setPerType(1);
        mqttUser.setPerId(userId);
        mqttUser.setImgUrl(user.getImgUrl());
        mqttUser.setPerName(user.getUserName());
        mqttUser.setIdcardper(user.getIdCard());
        log.info("发送的mqttuser为->{}", mqttUser);

        TUserOptionLog tUserOptionLog = new TUserOptionLog();
        String cmdBatchId = SnowFlakeUtil.getId();
        tUserOptionLog.setId(SnowFlakeUtil.getId());
        tUserOptionLog.setUserId(userId);
        /*1.人脸创建 2.人脸编辑 3.人脸删除 4.设备开门 5.设备关门6.授权*/
        tUserOptionLog.setOptionType(optionType);
        tUserOptionLog.setCmdBatchId(cmdBatchId);
        tUserOptionLog.setProjectId(user.getProjectId());
        tUserOptionLog.setArg(compareStr);
        userOptionLogService.save(tUserOptionLog);
        if (CollectionUtils.isNotEmpty(split)) {

            for (String sn : split) {
                log.info("创建人脸服务接口传入的sn为->{}", sn);
                //声明并设置id和请求id(雪花算法)
                //实际上这个是需要通过查表获取的设备的sn
                //合成人脸创建指令,cmd_id为请求记录id，client_id为设备sn
                JSONObject face = MqttCmdUtill.createFaceByUrl(sn, SnowFlakeUtil.getId(), mqttUser);
                //封装发送体
                /*1.人脸创建 2.人脸编辑 3.人脸删除 4.设备开门 5.设备关门 6.授权*/
                Send send = new Send();
                send.setCmd(face.toJSONString());
                send.setMqttType(optionType);
                send.setCreateUser(LoginUserUtils.getLoginUser().getId());
                send.setCmdBatchId(cmdBatchId);
                send.setTopic("face/" + sn + "/request");
                log.info("系统发送的创建人脸的指令是->{}", send);
                fegin.sendMessageWithTopic(send);
            }
        } else {
            log.error("创建人脸服务接口传入的sn为空");

        }

    }

    @Override
    public void updateUser(String userId, List<String> split,String compareStr) {

        if(StringUtils.isBlank(userId))
        {
            log.error("创建人脸服务接口传入的userId为空");
            return;
        }
        User user  = this.getById(userId);

        //封装请求体
        MqttUser mqttUser = new MqttUser();
        mqttUser.setFaceId(user.getId());
        mqttUser.setPerType(1);
        mqttUser.setPerId(userId);
        mqttUser.setImgUrl(user.getImgUrl());
        mqttUser.setPerName(user.getUserName());
        mqttUser.setIdcardper(user.getIdCard());
        log.info("发送的mqttuser为->{}", mqttUser);

        TUserOptionLog tUserOptionLog = new TUserOptionLog();
        String cmdBatchId = SnowFlakeUtil.getId();
        tUserOptionLog.setId(SnowFlakeUtil.getId());
        tUserOptionLog.setUserId(userId);
        /*1.人脸创建 2.人脸编辑 3.人脸删除 4.设备开门 5.设备关门 6.授权*/
        tUserOptionLog.setOptionType(2);
        tUserOptionLog.setCmdBatchId(cmdBatchId);
        tUserOptionLog.setProjectId(user.getProjectId());
        tUserOptionLog.setArg(compareStr);
        userOptionLogService.save(tUserOptionLog);

        if (CollectionUtils.isNotEmpty(split)) {

            for (String sn : split) {
                log.info("创建人脸服务接口传入的sn为->{}", sn);
                //声明并设置id和请求id(雪花算法)
                //实际上这个是需要通过查表获取的设备的sn
                //合成人脸创建指令,cmd_id为请求记录id，client_id为设备sn
                JSONObject face = MqttCmdUtill.createFaceByUrl(sn, SnowFlakeUtil.getId(), mqttUser);
                //封装发送体
                /*1.人脸创建 2.人脸编辑 3.人脸删除 4.设备开门 5.设备关门 6.授权*/
                Send send = new Send();
                send.setCmd(face.toJSONString());
                send.setMqttType(2);
                send.setCreateUser(LoginUserUtils.getLoginUser().getId());
                send.setCmdBatchId(cmdBatchId);
                send.setTopic("face/" + sn + "/request");
                log.info("系统发送的创建人脸的指令是->{}", send);
                fegin.sendMessageWithTopic(send);
            }
        } else {
            log.error("编辑人脸服务接口传入的sn为空");
        }

    }


    /*删除*/
    @Override
    public void deleteUser(List<String> bindDeviceSn, String userId, int type, String projectId ,Integer optionType) {
        TUserOptionLog tUserOptionLog = new TUserOptionLog();
        String cmdBatchId = SnowFlakeUtil.getId();
        tUserOptionLog.setId(SnowFlakeUtil.getId());
        tUserOptionLog.setUserId(userId);
        /*1.人脸创建 2.人脸编辑 3.人脸删除 4.设备开门 5.设备关门 6.授权*/
        tUserOptionLog.setOptionType(optionType);
        tUserOptionLog.setCmdBatchId(cmdBatchId);
        tUserOptionLog.setProjectId(projectId);
        userOptionLogService.save(tUserOptionLog);

        if (CollectionUtils.isNotEmpty(bindDeviceSn)) {
            for (String sn : bindDeviceSn) {
                //声明并设置id和请求id(雪花算法)
                //实际上这个是需要通过查表获取的设备的sn
                String client_id = sn;
                JSONObject deleteFaceByPerId = MqttCmdUtill.deleteFaceByPerId(client_id, SnowFlakeUtil.getId(), userId, type);
                String deleteCmd = deleteFaceByPerId.toJSONString();

                //封装指令状态表
                //封装发送体
                Send send = new Send();
                send.setCmd(deleteCmd);
                send.setMqttType(optionType);
                send.setCmdBatchId(cmdBatchId);
                send.setCreateUser(LoginUserUtils.getLoginUser().getId());
                send.setTopic("face/" + client_id + "/request");
                log.info("系统发送的创建人脸的指令是->{}", send);
                fegin.sendMessageWithTopic(send);
            }
        }else {
            log.info("删除人脸传入的设备sn为空");
        }
    }

    @Override
    public String getBatchIdByUserId(String userId) {
        LambdaQueryWrapper<TUserOptionLog> lambdaQueryWrapper = new LambdaQueryWrapper<>();
        lambdaQueryWrapper.eq(TUserOptionLog::getUserId,userId);
        TUserOptionLog one = userOptionLogService.getOne(lambdaQueryWrapper);
        String batchId = one.getCmdBatchId();
        return batchId;
    }

    @Override
    public List<String> QueryUserInitialEquipment(String floorId, String unitId, String buildingId, String areaId, String houseId) {
        //查询设备sn
        List<String> deviceList = new ArrayList<>();

        //查询设备sn
        if (StringUtils.isNotEmpty(houseId)) {
            LambdaQueryWrapper<TDevice> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(TDevice::getHouseId, houseId);
            List<TDevice> devices = deviceService.list(queryWrapper);
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        if (StringUtils.isNotEmpty(floorId)) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getFloorId, floorId));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }

        }
        if (StringUtils.isNotEmpty(unitId)) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getUnitId, unitId));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        if (StringUtils.isNotEmpty(buildingId)) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getBuildingId, buildingId));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        if (StringUtils.isNotEmpty(areaId)) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getAreaId, areaId));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        return deviceList;
    }

    @Override
    public List<String> QueryUserInitialEquipment(String userId) throws Exception {
        User user = this.getById(userId);
        if (null == user) {
            return null;
        }
        List<String> projectCodeList = LoginUserUtils.getProjectCodeList();
       if (!projectCodeList.contains( user.getProjectId())){
           throw new Exception("用户"+userId+"没有权限");
       }
        //查询设备sn
        List<String> deviceList = new ArrayList<>();
        if (StringUtils.isNotEmpty(user.getHouseId())) {
            LambdaQueryWrapper<TDevice> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(TDevice::getHouseId, user.getHouseId());
            List<TDevice> devices = deviceService.list(queryWrapper);
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        if (StringUtils.isNotEmpty(user.getFloorId())) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getFloorId, user.getFloorId()));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }

        }
        if (StringUtils.isNotEmpty(user.getUnitId())) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getUnitId, user.getUnitId()));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }

        }
        if (StringUtils.isNotEmpty(user.getBuildingId())) {
            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getBuildingId, user.getBuildingId()));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        if (StringUtils.isNotEmpty(user.getAreaId())) {

            List<TDevice> devices = deviceService.list(new LambdaQueryWrapper<TDevice>().eq(TDevice::getAreaId, user.getAreaId()));
            if (!devices.isEmpty()) {
                deviceList.addAll(devices.stream().map(TDevice::getDeviceSn).collect(Collectors.toList()));
            }
        }
        List<String> collect = deviceList.stream().distinct().collect(Collectors.toList());
        return collect;
    }

    @Override
    public String uploadImgWithBase64(HttpServletRequest req) throws IOException, ServletException {
        //图片处理
        String faceUrl = null;

            Part img = req.getPart("imgData");
            if (img != null) {
                log.info("！！！！！开始处理图片！！！！");
                InputStream inputStream = img.getInputStream();
                String message = IoUtil.readUtf8(inputStream);
                //上传阿里云,保存oss路径到实体类中
                try {
                    faceUrl = ossUtil.uploadBaseString2OSS(message);
                } catch (IOException e) {
                    log.error("上传人脸图片失败：" + e.getMessage());
                }
                log.info("人脸图片地址：" + faceUrl);
            } else {
                log.error("没有接收到图片信息");
            }
            log.info("!!!!!!!!!!!人员创建开始处理实体类！！！！！！！！！！！！！");
            //表单处理

        return faceUrl;
    }

    @Override
    public User encaUserwithServletRequset(HttpServletRequest req,String faceUrl) throws Exception {
        UserDto userDto = new UserDto();
        try {
            Part formData = req.getPart("formData");
            InputStream inputStream1 = formData.getInputStream();
            String message1 = IoUtil.readUtf8(inputStream1);
            userDto = JSONObject.parseObject(message1, UserDto.class);
        }catch (Exception e){
            log.error("人员添加转换表格数据发生错误",e);
            throw new Exception("人员添加转换表格数据发生错误"+e);

        }
//        //房屋信息模块
//        String projectId = userDto.getProjectId();
//        if (!LoginUserUtils.getProjectCodeList().contains(projectId)) {
//            throw new Exception("当前用户下不存在项目");
//        }
        //封装user实体类
        User user = new User();

        user.setUserName(userDto.getUserName());
        user.setCertType(userDto.getCertType());
        user.setMobile(userDto.getMobile());
        user.setIdCard(userDto.getIdCard());
        user.setImgUrl(faceUrl);
        user.setRemark(userDto.getRemark());
        user.setGender(userDto.getGender());

        user.setBirthday(userDto.getBirthday());
        user.setNation(userDto.getNation());
        user.setEthnic(userDto.getEthnic());
        user.setHometown(userDto.getHometown());
        user.setAddress(userDto.getAddress());

        user.setProjectId(userDto.getProjectId());
        user.setAreaId(userDto.getAreaId());
        user.setBuildingId(userDto.getBuildingId());
        user.setUnitId(userDto.getUnitId());
        user.setFloorId(userDto.getFloorId());
        user.setHouseId(userDto.getHouseId());
        user.setProjectUserTypeId(userDto.getProjectUserTypeId());
        user.setDepartmentId(userDto.getDepartmentId());

        if (userDto.getId()==null) {
            user.setId(SnowFlakeUtil.getId());
            user.setCreateUser(LoginUserUtils.getLoginUser().getId());
            user.setSysProjectCode(LoginUserUtils.getLoginUser().getOrgCode());
        }else{
            user.setId(userDto.getId());
        }
        return user;
    }

    @Override
    public String caseHttpRequst2String(HttpServletRequest req) throws IOException, ServletException {

        String diffStrs=null;
        Part diffStr = req.getPart("diffStr");
        InputStream inputStream2 = diffStr.getInputStream();
        diffStrs = IoUtil.readUtf8(inputStream2);
        return diffStrs;
    }


}
